#include "AudioDecoder.h"
#include <QDebug>
#include <inttypes.h>

extern "C" {
    #include <libavformat/avformat.h>
    #include <libavcodec/avcodec.h>
    #include <libavutil/avutil.h>
    #include <libavutil/mathematics.h>
    #include <libavutil/channel_layout.h>
    #include <libavutil/samplefmt.h>
    #include <libswresample/swresample.h>
    #include <libavfilter/avfilter.h>
    #include <libavfilter/buffersrc.h>
    #include <libavfilter/buffersink.h>
}


AudioDecoder::AudioDecoder()
    : m_formatContext(nullptr)
    , m_codecContext(nullptr)
    , m_audioStreamIndex(-1)
    , m_swrContext(nullptr)
    , m_filterGraph(nullptr)
    , m_filterSrc(nullptr)
    , m_filterSink(nullptr)
    , m_currentSpeed(1.0)
    , m_sampleRate(0)
    , m_channels(0)
    , m_durationMs(0)
    , m_isOpen(false)
{
    m_audioTimeBase.num = 0;
    m_audioTimeBase.den = 0;
    qDebug() << "[AudioDecoder] 创建音频解码器";
}

AudioDecoder::~AudioDecoder()
{
    closeAudio();
    qDebug() << "[AudioDecoder] 销毁音频解码器";
}

bool AudioDecoder::openAudio(const QString& audioPath)
{
    QMutexLocker locker(&m_mutex);
    if(m_isOpen)
    {
        closeAudio();
    }


    QByteArray pathBytes = audioPath.toUtf8();
    const char* path = pathBytes.constData();


    int ret=avformat_open_input(&m_formatContext,path,nullptr,nullptr);
    if(ret<0)
    {
        setError(QString("无法打开音频文件: %1").arg(audioPath),ret);
        return false;
    }

    ret=avformat_find_stream_info(m_formatContext,nullptr);
    if(ret<0)
    {
        setError(QString("无法找到音频流信息: %1").arg(audioPath),ret);
        return false;
    }

    //查找音频流
    m_audioStreamIndex=av_find_best_stream(m_formatContext,AVMEDIA_TYPE_AUDIO,-1,-1,nullptr,0);
    if(m_audioStreamIndex<0)
    {
        setError(QString("无法找到音频流: %1").arg(audioPath),ret);
        return false;
    }



    //获取音频流
    AVStream* audioStream=m_formatContext->streams[m_audioStreamIndex];
    if(!audioStream)
    {
        setError(QString("无效的音频流: %1").arg(audioPath),ret);
        return false;
    }

    //查找解码器
    const AVCodec* codec=avcodec_find_decoder(audioStream->codecpar->codec_id);
    if(!codec)
    {
        setError(QString("无法找到解码器: %1").arg(audioPath),ret);
        return false;
    }

    //分配解码器上下文
    m_codecContext=avcodec_alloc_context3(codec);
    if(!m_codecContext)
    {
        setError(QString("无法分配解码器上下文: %1").arg(audioPath),ret);
        return false;
    }    


    //复制参数

    ret=avcodec_parameters_to_context(m_codecContext,audioStream->codecpar);
    if(ret<0)
    {
        setError(QString("无法复制参数: %1").arg(audioPath),ret);
        return false;
    }

    //打开解码器
    ret=avcodec_open2(m_codecContext,codec,nullptr);
    if(ret<0)
    {
        setError(QString("无法打开解码器: %1").arg(audioPath),ret);
        return false;
    }

    //保存时间基准

    m_audioTimeBase=audioStream->time_base;

    //获取音频参数
    m_sampleRate=m_codecContext->sample_rate;
    m_channels=m_codecContext->ch_layout.nb_channels;


    //初始化重采样器
    if(!initResampler())
    {
        setError(QString("无法初始化重采样器: %1").arg(audioPath),ret);
        return false;
    }
    
    // 不使用滤镜（滤镜容易导致卡死），使用简单倍速方案
    qDebug() << "[AudioDecoder] 使用简单倍速方案（会变调，但稳定）";

    m_isOpen = true;
    
    qDebug() << "[AudioDecoder] 音频打开成功：" << audioPath;
    qDebug() << "  采样率：" << m_sampleRate << "Hz";
    qDebug() << "  声道数：" << m_channels;
    qDebug() << "  时长：" << m_durationMs << "ms";
    
    return true;

}

void AudioDecoder::closeAudio()
{
    QMutexLocker locker(&m_mutex);
    
    if (!m_isOpen) return;
    
    freeResources();
    
    m_sampleRate = 0;
    m_channels = 0;
    m_durationMs = 0;
    m_isOpen = false;
    m_error = "";
    m_audioStreamIndex = -1;
    
    qDebug() << "[AudioDecoder] 音频关闭";
}


AudioFrame AudioDecoder::decodeFrame(bool& isEof)
{
    QMutexLocker locker(&m_mutex);
    isEof = false;
    
    if (!m_isOpen) return AudioFrame();
    
    AVFrame* frame = av_frame_alloc();
    if (!frame) {
        setError(QString("无法分配AVFrame"));
        return AudioFrame();
    }
    
    AVPacket packet;
    av_init_packet(&packet);
    packet.data = nullptr;
    packet.size = 0;
    
    int readRet;
    while ((readRet = av_read_frame(m_formatContext, &packet)) == 0) {
        if (packet.stream_index == m_audioStreamIndex) {
            int ret = avcodec_send_packet(m_codecContext, &packet);
            if (ret < 0) {
                setError(QString("发送音频包失败"), ret);
                break;
            }
            
            ret = avcodec_receive_frame(m_codecContext, frame);
            if (ret == 0) {
                // 计算 pts
                int64_t ptsMs = 0;
                if (frame->pts != AV_NOPTS_VALUE) {
                    double sec = av_q2d(m_audioTimeBase) * frame->pts;
                    ptsMs = static_cast<int64_t>(sec * 1000);
                }
                
                // ========== 经过滤镜处理（倍速） ==========
                if (m_filterGraph && m_filterSrc && m_filterSink) {
                    // 1. 将解码帧推送到滤镜输入
                    ret = av_buffersrc_add_frame_flags(m_filterSrc, frame, AV_BUFFERSRC_FLAG_KEEP_REF);
                    if (ret < 0) {
                        setError("无法将帧推送到滤镜", ret);
                        av_frame_free(&frame);
                        av_packet_unref(&packet);
                        return AudioFrame();
                    }
                    
                    // 2. 从滤镜输出获取处理后的帧
                    AVFrame* filteredFrame = av_frame_alloc();
                    ret = av_buffersink_get_frame(m_filterSink, filteredFrame);
                    
                    if (ret == 0) {
                        // 释放原始帧，返回处理后的帧
                        av_frame_free(&frame);
                        av_packet_unref(&packet);
                        return AudioFrame(filteredFrame, ptsMs);
                    } else if (ret == AVERROR(EAGAIN)) {
                        // 滤镜需要更多输入，继续读取
                        av_frame_free(&filteredFrame);
                        av_frame_unref(frame);
                    } else {
                        // 滤镜错误
                        setError("从滤镜获取帧失败", ret);
                        av_frame_free(&filteredFrame);
                        av_frame_free(&frame);
                        av_packet_unref(&packet);
                        return AudioFrame();
                    }
                } else {
                    // 没有滤镜，直接返回原始帧
                    av_packet_unref(&packet);
                    return AudioFrame(frame, ptsMs);
                }
                
            } else if (ret != AVERROR(EAGAIN)) {
                setError(QString("接收音频帧失败"), ret);
                break;
            }
        }
        av_packet_unref(&packet);
    }
    
    if (readRet == AVERROR_EOF) {
        isEof = true;
        qDebug() << "[AudioDecoder] 到达文件末尾";
    } else if (readRet < 0) {
        setError("读取音频帧失败", readRet);
    }
    
    av_packet_unref(&packet);
    av_frame_free(&frame);
    
    return AudioFrame();
}

bool AudioDecoder::seek(int64_t positionMs)
{
    QMutexLocker locker(&m_mutex);

    if(!m_isOpen) return false;

    // 边界检查
    if (positionMs < 0) {
        positionMs = 0;
    }
    
    if (m_durationMs > 1000 && positionMs >= m_durationMs - 1000) {
        positionMs = m_durationMs - 1000;
    } else if (m_durationMs > 0 && positionMs >= m_durationMs) {
        positionMs = m_durationMs - 100;  // 留一点缓冲
    }
    
    // 确保最终位置不是负数
    if (positionMs < 0) {
        positionMs = 0;
    }

    int64_t seekPos = av_rescale_q(positionMs, AVRational{1, 1000}, m_audioTimeBase);

    if(m_codecContext)
    {
        avcodec_flush_buffers(m_codecContext);
    }

    int ret=av_seek_frame(m_formatContext, m_audioStreamIndex, seekPos, AVSEEK_FLAG_BACKWARD);
    if(ret<0)
    {
        setError(QString("跳转失败: %1").arg(positionMs),ret);
        return false;
    }

    qDebug() << "[AudioDecoder] 跳转成功: " << positionMs << "ms";
    return true;
}




int AudioDecoder::getSampleRate() const
{
    QMutexLocker locker(&m_mutex);
    return m_sampleRate;
}

int AudioDecoder::getChannels() const
{
    QMutexLocker locker(&m_mutex);
    return m_channels;
}

int64_t AudioDecoder::getDurationMs() const
{
    QMutexLocker locker(&m_mutex);
    return m_durationMs;
}

bool AudioDecoder::isOpened() const
{
    QMutexLocker locker(&m_mutex);
    return m_isOpen;
}


QString AudioDecoder::getError() const
{
    QMutexLocker locker(&m_mutex);
    return m_error;
}

SwrContext* AudioDecoder::getSwrContext() const
{
    QMutexLocker locker(&m_mutex);
    return m_swrContext;
}


void AudioDecoder::freeResources()
{
    // 释放滤镜
    freeFilter();
    
    if(m_swrContext)
    {
        swr_free(&m_swrContext);
        m_swrContext=nullptr;
    }

      
    if (m_codecContext) {
        avcodec_free_context(&m_codecContext);
        m_codecContext = nullptr;
    }
    
    if (m_formatContext) {
        avformat_close_input(&m_formatContext);
        m_formatContext = nullptr;
    }
}



void AudioDecoder::setError(const QString& error, int ffmpegErrCode)
{
    m_error = error;
    if (ffmpegErrCode != -1) {
        char errStr[AV_ERROR_MAX_STRING_SIZE] = {0};
        av_strerror(ffmpegErrCode, errStr, sizeof(errStr));
        m_error += QString("（FFmpeg错误：%1）").arg(errStr);
    }
    qDebug() << "[AudioDecoder] 错误：" << m_error;
}


bool AudioDecoder::initResampler()
{
    // 释放旧的重采样器（如果存在）
    if (m_swrContext) {
        swr_free(&m_swrContext);
        m_swrContext = nullptr;
    }
    
    AVChannelLayout outChLayout;
    if (m_channels == 1) {
        av_channel_layout_default(&outChLayout, 1);
    } else {
        av_channel_layout_default(&outChLayout, 2);
    }
    
    // 🎯 重采样器始终输出原始采样率（44100 Hz）
    // 变速是通过改变 SDL2 的播放采样率实现的，不是通过重采样
    int outputSampleRate = m_sampleRate;
    
    int ret = swr_alloc_set_opts2(
        &m_swrContext,
        &outChLayout,                           // 输出声道布局
        AV_SAMPLE_FMT_S16,                      // 输出格式
        outputSampleRate,                       // 🎯 输出采样率（根据倍速调整）
        &m_codecContext->ch_layout,             // 输入声道布局
        m_codecContext->sample_fmt,             // 输入格式
        m_codecContext->sample_rate,            // 输入采样率
        0, nullptr
    );
    
    if (ret < 0) {
        setError("无法创建重采样器", ret);
        return false;
    }
    
    ret = swr_init(m_swrContext);
    if (ret < 0) {
        setError("无法初始化重采样器", ret);
        return false;
    }
    
    qDebug() << "[AudioDecoder] 重采样器初始化成功";
    qDebug() << "  解码采样率：" << m_codecContext->sample_rate << "Hz";
    qDebug() << "  重采样输出：" << outputSampleRate << "Hz";
    return true;
}

// ==================== 音频滤镜相关函数 ====================

bool AudioDecoder::initFilter(double speed)
{
    // 限制倍速范围（atempo 支持 0.5 ~ 2.0）
    speed = qBound(0.5, speed, 2.0);
    m_currentSpeed = speed;
    
    qDebug() << "[AudioDecoder] 开始初始化音频滤镜，倍速：" << speed << "x";
    
    // 1. 创建滤镜图
    m_filterGraph = avfilter_graph_alloc();
    if (!m_filterGraph) {
        setError("无法分配滤镜图");
        return false;
    }
    
    // 2. 查找滤镜
    const AVFilter* bufferSrc = avfilter_get_by_name("abuffer");
    const AVFilter* bufferSink = avfilter_get_by_name("abuffersink");
    
    if (!bufferSrc || !bufferSink) {
        setError("无法找到音频滤镜");
        freeFilter();
        return false;
    }
    
    // 3. 构建 abuffer 参数（简化版，使用整数声道布局）
    char args[512];
    snprintf(args, sizeof(args),
             "time_base=1/%d:sample_rate=%d:sample_fmt=%d:channels=%d:channel_layout=0x%" PRIx64,
             m_codecContext->sample_rate,
             m_codecContext->sample_rate,
             m_codecContext->sample_fmt,
             m_codecContext->ch_layout.nb_channels,
             m_codecContext->ch_layout.u.mask);
    
    qDebug() << "[AudioDecoder] abuffer 参数：" << args;
    
    // 4. 创建输入滤镜（abuffer）
    int ret = avfilter_graph_create_filter(&m_filterSrc, bufferSrc, "in",
                                          args, nullptr, m_filterGraph);
    if (ret < 0) {
        setError("无法创建音频输入滤镜", ret);
        freeFilter();
        return false;
    }
    
    // 5. 创建输出滤镜（abuffersink）
    ret = avfilter_graph_create_filter(&m_filterSink, bufferSink, "out",
                                      nullptr, nullptr, m_filterGraph);
    if (ret < 0) {
        setError("无法创建音频输出滤镜", ret);
        freeFilter();
        return false;
    }
    
    // 6. 构建滤镜链字符串：atempo=speed
    char filterDesc[128];
    snprintf(filterDesc, sizeof(filterDesc), "atempo=%.2f", speed);
    
    qDebug() << "[AudioDecoder] 滤镜链：" << filterDesc;
    
    // 7. 解析并添加滤镜链
    AVFilterInOut* outputs = avfilter_inout_alloc();
    AVFilterInOut* inputs  = avfilter_inout_alloc();
    
    if (!outputs || !inputs) {
        setError("无法分配滤镜输入输出");
        avfilter_inout_free(&outputs);
        avfilter_inout_free(&inputs);
        freeFilter();
        return false;
    }
    
    outputs->name       = av_strdup("in");
    outputs->filter_ctx = m_filterSrc;
    outputs->pad_idx    = 0;
    outputs->next       = nullptr;
    
    inputs->name       = av_strdup("out");
    inputs->filter_ctx = m_filterSink;
    inputs->pad_idx    = 0;
    inputs->next       = nullptr;
    
    ret = avfilter_graph_parse_ptr(m_filterGraph, filterDesc, &inputs, &outputs, nullptr);
    
    avfilter_inout_free(&outputs);
    avfilter_inout_free(&inputs);
    
    if (ret < 0) {
        setError("无法解析滤镜链", ret);
        freeFilter();
        return false;
    }
    
    // 8. 配置滤镜图
    ret = avfilter_graph_config(m_filterGraph, nullptr);
    if (ret < 0) {
        setError("无法配置滤镜图", ret);
        freeFilter();
        return false;
    }
    
    qDebug() << "[AudioDecoder] ✅ 音频滤镜初始化成功，倍速：" << speed << "x";
    return true;
}

void AudioDecoder::freeFilter()
{
    if (m_filterGraph) {
        avfilter_graph_free(&m_filterGraph);
        m_filterGraph = nullptr;
        m_filterSrc = nullptr;
        m_filterSink = nullptr;
    }
}

bool AudioDecoder::setSpeed(double speed)
{
    QMutexLocker locker(&m_mutex);
    
    if (!m_isOpen) {
        qDebug() << "[AudioDecoder] 音频未打开，无法设置倍速";
        return false;
    }
    
    // 限制倍速范围（简单倍速支持更大范围）
    speed = qBound(0.25, speed, 4.0);
    
    if (qAbs(speed - m_currentSpeed) < 0.01) {
        qDebug() << "[AudioDecoder] 倍速已经是：" << speed << "x，跳过";
        return true;
    }
    
    qDebug() << "[AudioDecoder] 设置音频倍速：" << m_currentSpeed << "x → " << speed << "x（简单倍速，会变调）";
    
    // 更新倍速值
    double oldSpeed = m_currentSpeed;
    m_currentSpeed = speed;
    
    // 重新初始化重采样器（虽然采样率不变，但需要重新创建以清空缓冲区）
    bool success = initResampler();
    
    if (success) {
        qDebug() << "[AudioDecoder] ✅ 音频倍速调整成功：" << speed << "x";
        if (speed > 1.5) {
            qDebug() << "[AudioDecoder] ⚠️ 注意：声音会变尖（花栗鼠效果）";
        } else if (speed < 0.75) {
            qDebug() << "[AudioDecoder] ⚠️ 注意：声音会变低沉";
        }
    } else {
        qDebug() << "[AudioDecoder] ❌ 音频倍速调整失败，恢复原倍速";
        // 恢复原倍速
        m_currentSpeed = oldSpeed;
        initResampler();
    }
    
    return success;
}
